package com.hooper.hosp.service.impl;

import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.OSSException;
import com.hooper.hosp.service.OosService;
import com.hooper.hosp.utils.OosProperties;
import com.hooper.hospital.common.exception.HospitalException;
import com.hooper.hospital.common.result.ResultCodeEnum;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.joda.time.DateTime;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.*;
import java.util.Date;
import java.util.UUID;

import static com.hooper.hospital.common.constant.OosConstant.*;
import static com.hooper.hospital.common.result.ResultCodeEnum.*;

/**
 * @author Tim Hooper
 * @version 1.0
 * @time 2022/10/07/15:46
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class OosServiceImpl implements OosService {
    private final OosProperties oosProperties;

    @Override
    public String upload(MultipartFile file) {
        if (file == null) {
            throw new HospitalException(FILE_NOT_FOUND);
        }
        // oos 所属地
        String endpoint = oosProperties.getRegionUrl();
        // 阿里云账号AccessKey拥有所有API的访问权限，风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维，请登录RAM控制台创建RAM用户。
        String accessKeyId = oosProperties.getId();
        String accessKeySecret = oosProperties.getSecret();
        // 填写Bucket名称，例如example-bucket。
        String bucketName = oosProperties.getBucketName();
        // 填写Object完整路径，完整路径中不能包含Bucket名称，例如dir/example-object.txt。
        String originalFilename = file.getOriginalFilename();
        String fileType = originalFilename.substring(originalFilename.lastIndexOf('.'));
        log.info(fileType);
        //判断文件格式是否支持
        boolean isAllowed = false;
        for (String type : ALLOW_IMG_TYPE) {
            if (type.equals(fileType)) {
                isAllowed = true;
                break;
            }
        }
        if (!isAllowed) {
            throw new HospitalException(IMG_TYPE_NOT_ALLOW);
        }
        //将不同日期上传的证件进行分类
        String dirName = BASE_DIR_NAME + new DateTime().toString("yyyy/MM/dd") + "/";
        String imgName = dirName +
                UUID.randomUUID().toString().replaceAll("-", "") +
                System.currentTimeMillis() + fileType;

        //拼接图片url
        StringBuilder stringBuilder = new StringBuilder();
        for (int i = 0; i < endpoint.length(); i++) {
            char c = endpoint.charAt(i);
            if (c == '/') {
                i++;
                stringBuilder.append("//")
                        .append(bucketName)
                        .append(".");
            } else {
                stringBuilder.append(c);
            }
        }
        stringBuilder.append('/').append(imgName);
        // 创建OSSClient实例。
        OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
        try {
            InputStream inputStream = file.getInputStream();
            //上传图片
            ossClient.putObject(bucketName, imgName, inputStream);
        } catch (OSSException oe) {
            System.out.println("Caught an OSSException, which means your request made it to OSS, "
                    + "but was rejected with an error response for some reason.");
            System.out.println("Error Message:" + oe.getErrorMessage());
            System.out.println("Error Code:" + oe.getErrorCode());
            System.out.println("Request ID:" + oe.getRequestId());
            System.out.println("Host ID:" + oe.getHostId());
        } catch (ClientException ce) {
            System.out.println("Caught an ClientException, which means the client encountered "
                    + "a serious internal problem while trying to communicate with OSS, "
                    + "such as not being able to access the network.");
            System.out.println("Error Message:" + ce.getMessage());
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if (ossClient != null) {
                ossClient.shutdown();
            }
        }
        return stringBuilder.toString();
    }
}
